<template>
  <div class="select-group" v-bind="$attrs">
    <div class="select-group-selector">
      <el-select
        :multiple="multiple"
        value-key="id"
        :model-value="selectedValue"
        :disabled="disabled"
        :placeholder="placeholder"
        remote
        filterable
        clearable
        collapse-tags
        collapse-tags-tooltip
        @change="handleChange"
        @remote-method="handleRemoteMethod"
      >
        <el-option
          v-for="item in searchResults"
          :key="item.id"
          :label="item.name"
          :value="item.id"
          :disabled="item.disabled"
        >
          {{ item.name }}
        </el-option>
      </el-select>
    </div>

    <el-button :disabled="disabled" ghost @click="handleOpen">
      <template #icon><slot name="icon" /></template>
    </el-button>
  </div>
</template>

<script name="TreeSelect" lang="ts" setup>
  import { ref, computed, watchEffect } from 'vue';
  import { TreeSelectProps, type SSModelValue, type TData } from '../props';
  import { flatTreeData, genUserDeptsData } from '../utils';

  const props = defineProps(TreeSelectProps);

  const emits = defineEmits(['update:modelValue', 'change', 'openDailog']);

  const value = computed<SSModelValue>({
    get() {
      return props.modelValue;
    },
    set(val?: SSModelValue) {
      emits('update:modelValue', val);
      emits('change', val);
    }
  });

  const selectedValue = computed(() => {
    if (props.multiple) {
      if (!value.value) return [];
      return value.value?.map((item: TData) => item.id);
    }
    return (value.value as TData | undefined)?.id;
  });

  const showOptions = computed(() => {
    if (props.options == undefined) return [];
    if (props.type === 1) return flatTreeData(props.options);
    return genUserDeptsData(props.options);
  });

  const searchResults = ref<Array<any>>([]);

  const handleRemoteMethod = (key: string) => {
    if (key) {
      searchResults.value = showOptions.value.filter((obj) => {
        if (!(obj as TData).name) return false;
        return (obj as TData).name
          .toLocaleLowerCase()
          .includes(key.toLocaleLowerCase());
      });
    } else {
      searchResults.value = showOptions.value;
    }
  };

  const handleOpen = () => {
    if (props.disabled) return;
    emits('openDailog');
  };

  const handleChange = (el?: string | string[]) => {
    if (!el) value.value = undefined;
    else if (props.multiple) {
      value.value = showOptions.value.filter((item) =>
        (el as string[]).includes((item as TData)!.id)
      ) as SSModelValue;
    } else {
      value.value = showOptions.value.find((item) => (item as TData).id === el);
    }
  };

  watchEffect(() => {
    searchResults.value = showOptions.value;
  });
</script>

<style scoped lang="less">
  .select-group {
    width: 100%;
    display: flex;
    align-items: center;
    flex-direction: row;

    &-selector {
      flex: 1;
      margin-right: 12px;
      width: 200px;
    }
  }
</style>
